const crypto = require('crypto')
const contentType = require('content-type')
const getRawBody = require('raw-body')
const convert = require('xml-js')
const axios = require('axios')
const randomstring = require("randomstring")
const querystring = require('querystring')

const auth = (ctx, next) => {
  // 验证是否是微信公众号访问的我
  const token = 'weixin'

  let {
    signature,
    echostr,
    timestamp,
    nonce
  } = ctx.request.query

  const str = [token, timestamp, nonce].sort().join('')
  const sign = crypto.createHash('sha1').update(str).digest('hex')

  if (sign === signature) {
    ctx.body = echostr
  } else {
    ctx.body = 'error'
  }
}

const autoreply = async (ctx, next) => {
  const text = (await getRawBody(ctx.req, {
    length: ctx.req.headers['content-length'],
    limit: '1mb',
    encoding: contentType.parse(ctx.req).parameters.charset
  })).toString()

  const result = convert.xml2js(text, {
    compact: true,
    textKey: 'value',
    cdataKey: 'value'
  }).xml

  const {
    ToUserName,
    FromUserName,
    CreateTime,
    MsgType,
    Content,
    MsgId
  } = Object.keys(result).reduce((obj, key) => {
    obj[key] = result[key]['value']
    return obj
  }, {})

  await ctx.render('weixin', {
    ToUserName: FromUserName,
    FromUserName: ToUserName,
    CreateTime: new Date().getTime(),
    MsgType: 'text',
    Content: '<a href="http://raink.net/">JSAPI-TEST</a>'
  })
  
  next()
}

const sign = async (ctx, next) => {
  // APPID
  const appid = 'wx7ba8ee8a8beace33'
  // Secret
  const secret = 'd62705bd6fdf27441397683019077e20'

  // 获取access_token
  const url = `https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=${appid}&secret=${secret}`
  const result_at = await axios.get(url)
  const { access_token } = result_at.data
  
  // 获取jsapi_ticket
  const url2 = `https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token=${access_token}&type=jsapi`
  const result_jt = await axios.get(url2)
  const jsapi_ticket = result_jt.data.ticket
  
  // 生成签名
  // noncestr（随机字符串）
  const noncestr = randomstring.generate(32)
  // timestamp（时间戳）
  const timestamp = Math.floor(new Date().getTime()/1000)
  // 当前网页的url
  const current_url = 'http://raink.net/'
  
  const signObj = {
    noncestr,
    url: current_url,
    timestamp,
    jsapi_ticket
  }
  const orderedSignObj = Object.keys(signObj).sort().reduce((obj, key) => {
    obj[key] = signObj[key]
    return obj
  }, {})

  const string1 = querystring.stringify(orderedSignObj, null, null, {
    encodeURIComponent: str => str
  })

  const signature = crypto.createHash('sha1').update(string1).digest('hex')

  ctx.body = {
    appId: appid,
    timestamp,
    nonceStr: noncestr,
    signature
  }
}

module.exports = {
  auth,
  autoreply,
  sign
}